﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Input;
using LGE;

namespace YouOnlyGetOne
{
    public class Player : GameObject
    {
        public Vector2 CameraOffset { get { return drawPosition - position; } }

        bool isWalking = false;
        new Vector2 direction = Direction.Down;

        public SpriteSheetState state;
        public float moveSpeed = 7;
        public Cue walkCue;

        public double stunTimer = -1;
        double stunDuration = 500;

        // stats
        public int keys = 0;
        public int coins = 0;
        public int points = 0;

        public Player(PlayScreen ps)
            : base(ps, GameObject.tile)
        {
            HitBox = new Rectangle(0, 20, 64, 74);
            drawPosition = new Vector2(1280 / 2, 720 / 2);
            state = new SpriteSheetState(this);
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stand_D"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stand_U"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stand_R"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stand_R"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\walk_D"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\walk_U"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\walk_R"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\walk_R"), new SpriteSheet(this, 128, 128, 40, true));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stun_D"), new SpriteSheet(this, 128, 128, 40, false));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stun_U"), new SpriteSheet(this, 128, 128, 40, false));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stun_R"), new SpriteSheet(this, 128, 128, 40, false));
            state.Add(Engine.Load<Texture2D>("Images\\Character\\stun_R"), new SpriteSheet(this, 128, 128, 40, false));
            state.Change(States.StandU);
            state.Change(States.StandD);
            
            walkCue = Audio.GetCue("char_walk");
            walkCue.Play();
        }

        public override void Update(GameTime gameTime)
        {
            speed = new Vector2(0, 0);

            if (stunTimer >= 0)
            {
                state.Change(8 + (direction == Direction.Down ? 0 : direction == Direction.Up ? 1 : direction == Direction.Right ? 2 : 3));
                state.Update(gameTime);
                stunTimer += gameTime.ElapsedGameTime.TotalMilliseconds;
                if (stunTimer > stunDuration) stunTimer = -1;
                return;
            }

            UpdateInput(gameTime);

            //if (CheckCollisionWithDeath()) Die();
            CheckCollisionWithMap(MapManager.CollisionLayer);

            //if (HitBox.Intersects(ps.ExitRect)) { walkCue.Dispose(); Audio.DisposeAll(); GameScreenManager.ChangeScreen(new Scene2(ps.map)); }

            state.Update(gameTime);
        }

        public bool CheckCollisionWithDeath()
        {
            bool collided = false;

            position.Y += 1f;
            collided = (MapManager.CollisionH(this, ps.map, MapManager.DeathLayer, speed.X < 0) != 0) ||
                       (MapManager.CollisionV(this, ps.map, MapManager.DeathLayer, speed.Y < 0) != 0);
            position.Y -= 1f;

            return collided;
        }

        private void UpdateInput(GameTime gameTime)
        {
            if (!alive)
            {
                GameScreenManager.ChangeScreen(new StartScreen());
                return;
            }

            // movimento
            if (Input.Down(KeyMap.Left))
            {
                speed.X = -moveSpeed;
                isWalking = true;
                direction = Direction.Left;
            }
            else if (Input.Down(KeyMap.Right))
            {
                speed.X = moveSpeed;
                isWalking = true;
                direction = Direction.Right;
            }
            else if (Input.Down(KeyMap.Up))
            {
                speed.Y = -moveSpeed;
                isWalking = true;
                direction = Direction.Up;
            }
            else if (Input.Down(KeyMap.Down))
            {
                speed.Y = moveSpeed;
                isWalking = true;
                direction = Direction.Down;
            }
            else isWalking = false;

            // SFX char_walk
            if (speed.Length() > 0)
                walkCue.Resume();
            else 
                walkCue.Pause();

            state.Change((isWalking ? 4 : 0) + (direction == Direction.Down ? 0 : direction == Direction.Up ? 1 : direction == Direction.Right ? 2 : 3));
        }

        public override void Draw(SpriteBatch spriteBatch)
        {
            spriteBatch.Draw(sprite, drawPosition + new Vector2(0, 0), sourceRectangle, Color.White, rotation, origin, scale,
                state.actualState == States.StandL || state.actualState == States.WalkL || state.actualState == States.StunL ? SpriteEffects.FlipHorizontally : SpriteEffects.None, 0);

            //if (YOGO.isDebugMode) DrawCollidingTiles(spriteBatch);
            if (YOGO.isDebugMode) DrawHitBox(spriteBatch);
        }

        public void Die()
        {
            if (!alive) return;
            //walkCue.Dispose();
            //Audio.bgmCue.Pause();
            //Audio.PlayCue("char_die");
            alive = false;
        }

        public static class States
        {
            public const int StandD = 0;
            public const int StandU = 1;
            public const int StandR = 2;
            public const int StandL = 3;
            public const int WalkD = 4;
            public const int WalkU = 5;
            public const int WalkR = 6;
            public const int WalkL = 7;
            public const int StunD = 8;
            public const int StunU = 9;
            public const int StunR = 10;
            public const int StunL = 11;
        }
    }
}
